﻿using System;
using System.Collections.Generic;
using System.Linq;
using System.Web;
using umbraco.cms.businesslogic.web;
using umbraco.cms.businesslogic;
using umbraco.BusinessLogic.console;
using umbraco;
using System.Xml.XPath;
using umbraco.cms.businesslogic.property;

namespace AutoFolders.Providers
{
    public class DateFolderProvider : BaseFolderProvider
    {
        private string m_dayFormat = null;
        private string m_monthFormat = null;
        private string m_yearFormat = null;
        private string m_folderDocTypeAlias = null;
        private bool m_includeDayLevel = false;

        public string DayFormat
        {
            get
            {
                if (m_dayFormat == null)
                {
                    if (base.Properties.ContainsKey("DayFormat"))
                    {
                        m_dayFormat = base.Properties["DayFormat"];
                        m_includeDayLevel = true;
                    }
                    else
                        m_dayFormat = "dd";
                }

                return m_dayFormat;
            }
        }

        public string MonthFormat
        {
            get
            {
                if (m_monthFormat == null)
                {
                    if (base.Properties.ContainsKey("MonthFormat"))
                        m_monthFormat = base.Properties["MonthFormat"];
                    else
                        m_monthFormat = "MM";
                }

                return m_monthFormat;
            }
        }

        public string YearFormat
        {
            get
            {
                if (m_yearFormat == null)
                {
                    if (base.Properties.ContainsKey("YearFormat"))
                        m_yearFormat = base.Properties["YearFormat"];
                    else
                        m_yearFormat = "yyyy";
                }

                return m_yearFormat;
            }
        }

        public override int CreatedFolderDepth
        {
            get
            {
                string temp = DayFormat;
                return (m_includeDayLevel) ? 3 : 2;
            }
        }

        public DateTime GetDocumentDateTime(Document newDocument)
        {
            string dateField = "@CreateDate";
            DateTime documentDateTime = DateTime.MinValue;

            if (base.Properties.ContainsKey("DateField"))
                dateField = base.Properties["DateField"];
             
            if (dateField == "@CreateDate")
                documentDateTime = newDocument.CreateDateTime;
            else if (dateField == "@ExpiryDate")
                documentDateTime = newDocument.ExpireDate;
            else if (dateField == "@ReleaseDate")
                documentDateTime = newDocument.ReleaseDate;
            else if (dateField == "@UpdateDate")
                documentDateTime = newDocument.UpdateDate;
            else if (dateField == "@VersionDate")
                documentDateTime = newDocument.VersionDate;
            else
            {
                foreach (Property prop in newDocument.getProperties)
                {
                    if (prop.PropertyType.Alias == dateField)
                    {
                        if (prop.Value != null && !String.IsNullOrEmpty(prop.Value.ToString()))
                        {
                            documentDateTime = Convert.ToDateTime(prop.Value);
                        }
                        break;
                    }
                }
            };

            return documentDateTime;
        }

        #region IFolderProvider Members

        public override int FindValidFolderId(Document newDocument, int iNodeRootFolder)
        {
            DateTime dateTime = GetDocumentDateTime(newDocument);
            string currentDay = dateTime.ToString(DayFormat);
            string currentMonth = dateTime.ToString(MonthFormat);
            string currentYear = dateTime.ToString(YearFormat);
            int validFolderId = -1;

            if (newDocument.Level > 1)
            {
                CMSNode parentNode = new CMSNode(iNodeRootFolder);

                // Return root if data couldn't be determined
                if (dateTime == DateTime.MinValue)
                    return parentNode.Id;

                // Firstly, check if user is adding document to auto-created folder (e.g. 2009/09)
                if (!m_includeDayLevel && parentNode.Level > 1)
                {
                    CMSNode grandParentDocument = parentNode.Parent;

                    if (parentNode.Text == currentMonth && grandParentDocument.Text == currentYear)
                        return parentNode.Id;
                }
                else if (m_includeDayLevel && parentNode.Level > 2)
                {
                    CMSNode grandParentDocument = parentNode.Parent;
                    CMSNode grandParentDocument2 = grandParentDocument.Parent;

                    if (parentNode.Text == currentDay && grandParentDocument.Text == currentMonth && grandParentDocument2.Text == currentYear)
                        return parentNode.Id;
                }


                // Secondly check for child folder that was previously auto-created
                foreach (IconI yearIcon in parentNode.Children)
                {
                    if (yearIcon.Text == currentYear)
                    {
                        foreach (IconI monthIcon in yearIcon.Children)
                        {
                            if (!m_includeDayLevel && monthIcon.Text == currentMonth)
                            {
                                validFolderId = monthIcon.Id;
                                break;
                            }
                            else if (monthIcon.Text == currentMonth)
                            {
                                foreach (IconI dayIcon in monthIcon.Children)
                                {

                                    if (dayIcon.Text == currentDay)
                                    {
                                        validFolderId = dayIcon.Id;
                                        break;
                                    }
                                }
                            }

                        }
                    }
                }
            }

            return validFolderId;
        }

        public override int CreateFolderStructure(Document newDocument, int iNodeRootFolder, string folderDocTypeAlias)
        {
            DateTime dateTime = GetDocumentDateTime(newDocument);

            string currentDay = dateTime.ToString(DayFormat);
            string currentMonth = dateTime.ToString(MonthFormat);
            string currentYear = dateTime.ToString(YearFormat);

            // Check if YEAR folder has already been created.
            int yearDocumentId = -1;
            int rootDocumentId = -1;
            if (newDocument.Level > 1)
            {
                CMSNode parentNode = new CMSNode(iNodeRootFolder);

                rootDocumentId = parentNode.Id;
                foreach (IconI ni in parentNode.Children)
                {
                    if (ni.Text == currentYear)
                    {
                        yearDocumentId = ni.Id;
                        break;
                    }
                }
            }
            if (yearDocumentId <= 0)
            {
                Document document = Document.MakeNew(currentYear, DocumentType.GetByAlias(folderDocTypeAlias), newDocument.User, rootDocumentId);
                document.Publish(newDocument.User);
                library.UpdateDocumentCache(document.Id);
                yearDocumentId = document.Id;
            }

            if (!m_includeDayLevel) // Immediately create month folder
            {
                Document document2 = Document.MakeNew(currentMonth, DocumentType.GetByAlias(folderDocTypeAlias), newDocument.User, yearDocumentId);
                document2.Publish(newDocument.User);
                library.UpdateDocumentCache(document2.Id);

                return document2.Id;
            }
            else // check for month folder, then create day folder
            {
                CMSNode yearIcon = new CMSNode(yearDocumentId);
                int monthDocumentId = -1;

                foreach (IconI monthIcon in yearIcon.Children)
                {
                    if (monthIcon.Text == currentMonth)
                    {
                        monthDocumentId = monthIcon.Id;
                        break;
                    }
                }

                if (monthDocumentId <= 0)
                {
                    Document document2 = Document.MakeNew(currentMonth, DocumentType.GetByAlias(folderDocTypeAlias), newDocument.User, yearDocumentId);
                    document2.Publish(newDocument.User);
                    library.UpdateDocumentCache(document2.Id);
                    monthDocumentId = document2.Id;
                }


                Document document3 = Document.MakeNew(currentDay, DocumentType.GetByAlias(folderDocTypeAlias), newDocument.User, monthDocumentId);
                document3.Publish(newDocument.User);
                library.UpdateDocumentCache(document3.Id);

                return document3.Id;
            }
        }

        #endregion
    }
}
